/*
 * rfm23.c
 *
 *  Created on: 01.12.2011
 *      Author: alexs
 */

#include "stm32f10x.h"
#include "stm32f10x_conf.h"

#include "main.h"
#include "rfm23.h"

#if !defined(ARRAY_SIZE)
#define ARRAY_SIZE(x) (sizeof((x)) / sizeof((x)[0]))
#endif

const rfm_init_struct_t rfm_init_struct_tx[]={
		{RFM23_06_Interrupt_Enable_2,0},
		{RFM23_07_Operating_Mode_and_Function_Control_1,RFM23_mode_READY},
		{RFM23_09_30_MHz_Crystal_Oscillator_Load_Capacitance,0x7f},
		{RFM23_0A_Microcontroller_Output_Clock,0x05},
		{RFM23_0B_GPIO_Configuration_0,0x34},
		{RFM23_0C_GPIO_Configuration_1,0x3b},
		{RFM23_0D_GPIO_Configuration_2,0x39},
		{RFM23_0E_I_O_Port_Configuration,0},
		{RFM23_6D_TX_Power,0x0f},

		{RFM23_1C_IF_Filter_Bandwidth, 0x05},
		{RFM23_1D_AFC_Loop_Gearshift_Override, 0x40},
		{RFM23_20_Clock_Recovery_Oversampling_Rate, 0xC8},
		{RFM23_21_Clock_Recovery_Offset_2, 0x00},
		{RFM23_22_Clock_Recovery_Offset_1, 0xA3},
		{RFM23_23_Clock_Recovery_Offset_0, 0xD7},
		{RFM23_24_Clock_Recovery_Timing_Loop_Gain_1, 0x10},
		{RFM23_25_Clock_Recovery_Timing_Loop_Gain_0, 0x94},
		{RFM23_2A_AFC_Limiter, 0x24},
		{RFM23_2C_OOK_Counter_Value_1, 0x28},
		{RFM23_2D_OOK_Counter_Value_2, 0x3E},
		{RFM23_2E_Slicer_Peak_Holder, 0x2A},
		{RFM23_30_Data_Access_Control, 0x8C},
		{RFM23_32_Header_Control_1, 0xF0},
		{RFM23_33_Header_Control_2, 0x46},
		{RFM23_34_Preamble_Length, 0x10},
		{RFM23_35_Preamble_Detection_Control_1, 0x22},
		{RFM23_36_Synchronization_Word_3, 0x4D},
		{RFM23_37_Synchronization_Word_2, 0x47},
		{RFM23_38_Synchronization_Word_1, 0x50},
		{RFM23_39_Synchronization_Word_0, 0x53},
		{RFM23_3A_Transmit_Header_3, 0x41},
		{RFM23_3B_Transmit_Header_2, 0x6C},
		{RFM23_3C_Transmit_Header_1, 0x65},
		{RFM23_3D_Transmit_Header_0, 0x78},
		{RFM23_3E_Packet_Length, 0x10},
		{RFM23_3F_Check_Header_3, 0x41},
		{RFM23_40_Check_Header_2, 0x6C},
		{RFM23_41_Check_Header_1, 0x65},
		{RFM23_42_Check_Header_0, 0x78},
		{RFM23_43_Header_Enable_3, 0xFF},
		{RFM23_44_Header_Enable_2, 0xFF},
		{RFM23_45_Header_Enable_1, 0xFF},
		{RFM23_46_Header_Enable_0, 0xFF},
		{RFM23_6E_TX_Data_Rate_1, 0xA3},
		{RFM23_6F_TX_Data_Rate_0, 0xD7},
		{RFM23_70_Modulation_Mode_Control_1, 0x29},
		{RFM23_71_Modulation_Mode_Control_2, 0x23},
		{RFM23_72_Frequency_Deviation, 0x48},
		{RFM23_75_Frequency_Band_Select, 0x73},
		{RFM23_76_Nominal_Carrier_Frequency_1, 0x00},
		{RFM23_77_Nominal_Carrier_Frequency_0, 0x00},
		};

const rfm_init_struct_t rfm_init_struct_rx[]={
		{RFM23_06_Interrupt_Enable_2,0},
		{RFM23_07_Operating_Mode_and_Function_Control_1,RFM23_mode_READY},
		{RFM23_09_30_MHz_Crystal_Oscillator_Load_Capacitance,0x7f},
		{RFM23_0A_Microcontroller_Output_Clock,0x05},
		{RFM23_0B_GPIO_Configuration_0,0x34},
		{RFM23_0C_GPIO_Configuration_1,0x3b},
		{RFM23_0D_GPIO_Configuration_2,0x39},
		{RFM23_0E_I_O_Port_Configuration,0},
		{RFM23_70_Modulation_Mode_Control_1,0x20},
		{RFM23_1D_AFC_Loop_Gearshift_Override,0},
		{RFM23_1C_IF_Filter_Bandwidth,0x1d},
		{RFM23_20_Clock_Recovery_Oversampling_Rate,0x41},
		{RFM23_21_Clock_Recovery_Offset_2,0x60},
		{RFM23_22_Clock_Recovery_Offset_1,0x27},
		{RFM23_23_Clock_Recovery_Offset_0,0x52},
		{RFM23_24_Clock_Recovery_Timing_Loop_Gain_1,0},
		{RFM23_25_Clock_Recovery_Timing_Loop_Gain_0,0x06},
		{RFM23_2A_AFC_Limiter,0x1e},
		{RFM23_30_Data_Access_Control,0x8c},
		{RFM23_32_Header_Control_1,0xFF},
		{RFM23_33_Header_Control_2,0x42},
		{RFM23_34_Preamble_Length,64},
		{RFM23_35_Preamble_Detection_Control_1,0x20},
		{RFM23_36_Synchronization_Word_3,0x2d},
		{RFM23_37_Synchronization_Word_2,0xd4},
		{RFM23_38_Synchronization_Word_1,0},
		{RFM23_39_Synchronization_Word_0,0},
		{RFM23_3F_Check_Header_3, 's'},
		{RFM23_40_Check_Header_2, 'o'},
		{RFM23_41_Check_Header_1, 'n'},
		{RFM23_42_Check_Header_0, 'g'},
		{RFM23_43_Header_Enable_3,0xff},
		{RFM23_44_Header_Enable_2,0xff},
		{RFM23_45_Header_Enable_1,0xff},
		{RFM23_46_Header_Enable_0,0xff},
		{RFM23_79_Frequency_Hopping_Channel_Select,0},
		{RFM23_7A_Frequency_Hopping_Step_Size,0},
		{RFM23_71_Modulation_Mode_Control_2,0x23},
		{RFM23_72_Frequency_Deviation,0x38},
		{RFM23_73_Frequency_Offset_1,0},
		{RFM23_74_Frequency_Offset_2,0},
		{RFM23_75_Frequency_Band_Select, 0x73},
		{RFM23_76_Nominal_Carrier_Frequency_1, 0x0},
		{RFM23_77_Nominal_Carrier_Frequency_0, 0x0},
//		{RFM23_7E_RX_FIFO_Control, 1},

};

uint8_t SPI_talk(SPI_dir dir, const uint8_t addr, const uint8_t val){
	uint16_t tmp=0;

	if (dir==READ) tmp=(addr&0x7f); else tmp=(addr|0x80);
	tmp=(tmp<<8)|(val);
	while (SPI_I2S_GetFlagStatus(SPI1,SPI_I2S_FLAG_TXE)==RESET);
	GPIO_ResetBits(GPIOA,GPIO_Pin_4);
	SPI_I2S_SendData(SPI1,tmp);
	while (SPI_I2S_GetFlagStatus(SPI1,SPI_I2S_FLAG_RXNE)==RESET);
	tmp=SPI_I2S_ReceiveData(SPI1);
	GPIO_SetBits(GPIOA,GPIO_Pin_4);
	return (tmp&0xff);
}

void RFM23_Init(uint8_t tx) {
	uint8_t i;
	RFM23_clear_intterrupt();
	if (tx) {
		for (i=0;i<(ARRAY_SIZE(rfm_init_struct_tx));i++) SPI_talk(WRITE,rfm_init_struct_tx[i].addr,rfm_init_struct_tx[i].value);
	}else{
		for (i=0;i<(ARRAY_SIZE(rfm_init_struct_rx));i++) SPI_talk(WRITE,rfm_init_struct_rx[i].addr,rfm_init_struct_rx[i].value);
	}
}
